
#include "Upgrader.h"
#include <event2/http.h>
#include <event2/util.h>
#include "../WebsockerErrorcode.h"
#include "../../http/Request.h"
#include "../../http/httpserver/ResponseWriter.h"
#include "../utils.h"


Upgrader::Upgrader(std::shared_ptr<Request> r, std::shared_ptr<ResponseWriter> w)
{
    loop_ = w->loop_;
    req_ = r;
    rsp_ = w;
}

WebsocketConnPtr Upgrader::upgrade(std::error_code& e)
{
    if (req_->Method != "GET") {
        e = make_ws_error_code(ws_error::method_not_get);
        return nullptr;
    }
    if(evutil_ascii_strcasecmp(req_->Header["Connection"].c_str(), "upgrade") != 0){
        e = make_ws_error_code(ws_error::header_no_connect);
        return nullptr;
    } 
    if (evutil_ascii_strcasecmp(req_->Header["Upgrade"].c_str(), "websocket") != 0) {
        e = make_ws_error_code(ws_error::header_no_upgrade);
        return nullptr;
    }
    if (req_->Header["Sec-Websocket-Version"] != "13") {
        e = make_ws_error_code(ws_error::ws_version_error);
        return nullptr;
    }
    if (req_->Header["Sec-Websocket-Key"].empty()) {
        e = make_ws_error_code(ws_error::header_no_sec_key);
        return nullptr;
    }

    
    rsp_->set_header("Upgrade", "websocket");
    rsp_->set_header("Connection", "Upgrade");
    rsp_->set_header("Sec-WebSocket-Accept", compute_accept_key(req_->Header["Sec-Websocket-Key"]));
    rsp_->write(HTTPStatus::StatusSwitchingProtocols, "");
    
    WebsocketConnPtr conn = std::make_shared<WebsocketConn>();
    // hook bufferevent.
    e = conn->hook(loop_, req_);
    if (e) {
        return nullptr;
    }
    return conn;
}


